// 地图类
import {AcGameObject} from "@/assets/scripts/AcGameObject";

import {Wall} from "@/assets/scripts/Wall";
import {Snake} from "@/assets/scripts/Snake";

export class GameMap extends AcGameObject {
    //ctx       画布
    //parent    画布的父元素
    constructor(ctx, parent, store) {
        super();

        this.ctx = ctx;
        this.parent = parent;
        this.store = store;
        this.L = 0;                     //地图的大小随游览器的大小动态变化

        this.rows = 13;
        this.cols = 14;

        this.walls = [];                //存储生成的障碍物
        this.inner_walls_count = 30;    //生成的障碍物的数量

        //创建两条蛇
        this.snakes = [
            new Snake({id: 0, color: "#4876EC", r: this.rows - 2, c: 1}, this),
            new Snake({id: 1, color: "#F94848", r: 1, c: this.cols - 2}, this),
        ];
    }

    //判断两条蛇的下一步状态
    check_ready() {
        for (const snake of this.snakes) {
            if (snake.status !== "idle") return false;
            if (snake.direction === -1) return false;
        }
        return true;
    }

    //创建障碍物
    create_walls() {

        //直接从全局变量获取
        const g = this.store.state.pk.game_map;

        //创建障碍物
        for (let r = 0; r < this.rows; r++) {
            for (let c = 0; c < this.cols; c++) {
                if (g[r][c])
                    this.walls.push(new Wall(r, c, this))
            }
        }
    }

    //添加蛇的移动监控
    add_listening_event() {

        //判断是否是录像回放
        if (this.store.state.record.is_record === true) {

            let k = 0;
            let [snake0, snake1] = this.snakes;
            let a_steps = this.store.state.record.a_steps;
            let b_steps = this.store.state.record.b_steps;
            let record_loser = this.store.state.record.record_loser;

            //定时函数
            const interval_id = setInterval(() => {
                //判断当前是否是最后一步
                if (k >= a_steps.length - 1) {
                    //判断当前蛇的状态
                    if (record_loser === "all" || record_loser === "A") {
                        snake0.status = "die";
                    }
                    if (record_loser === "all" || record_loser === "B") {
                        snake1.status = "die";
                    }
                    clearInterval(interval_id);
                } else {
                    snake0.set_direction(parseInt(a_steps[k]));
                    snake1.set_direction(parseInt(b_steps[k]));
                }
                k++;
            }, 350);
        } else {
            this.ctx.canvas.focus();        //聚焦

            this.ctx.canvas.addEventListener("keydown", e => {
                let direction = -1;
                if (e.key === 'w') direction = 0;
                else if (e.key === 'd') direction = 1;
                else if (e.key === 's') direction = 2;
                else if (e.key === 'a') direction = 3;

                if (direction >= 0) {      //已经接收到用户操作,则发送WebSocket连接
                    //前端向后端发消息： 前端 -> 后端
                    this.store.state.pk.socket.send(
                        JSON.stringify({
                            "event": "move",
                            "direction": direction
                        })
                    )
                }
            })
        }
    }

    start() {
        //创建地图
        this.create_walls();
        //添加监听函数
        this.add_listening_event();
    }

    //更新一下正方形的边长(内正方形)
    update_size() {
        //只读属性 Element.clientWidth 对于内联元素以及没有 CSS 样式的元素为 0；
        // 否则，它是元素内部的宽度（以像素为单位）。
        //可以简单理解为求div的长宽函数!!!
        this.L = parseInt(Math.min(this.parent.clientWidth / this.cols, this.parent.clientHeight / this.rows));
        this.ctx.canvas.width = this.L * this.cols;
        this.ctx.canvas.height = this.L * this.rows;
        // console.log(this.L, this.ctx.canvas.width, this.ctx.canvas.height);
    }

    //让两条蛇都进入下一回合
    next_step() {
        for (const snake of this.snakes)
            snake.next_step();
    }

    check_valid(cell) {  // 检测目标位置是否合法：没有撞到两条蛇的身体和障碍物
        for (const wall of this.walls) {        //枚举所有的墙
            if (wall.r === cell.r && wall.c === cell.c) {
                return false;
            }
        }

        //枚举所有的蛇
        //1. 自己的下一步是否碰到蛇身
        //2. 别人的下一步是否碰到我的蛇身
        for (const snake of this.snakes) {
            let k = snake.cells.length;         //得到蛇的身体
            if (!snake.check_tail_increasing()) //当蛇尾会前进的时候(蛇头就可以前进了)，蛇尾不要判断
                k--;
            for (let i = 0; i < k; i++)
                if (snake.cells[i].r === cell.r && snake.cells[i].c === cell.c)
                    return false;
        }
        return true;
    }

    update() {
        this.update_size()
        //判断两条蛇是否都准备好了
        if (this.check_ready())
            this.next_step()
        this.render();
    }

    //渲染函数(绘制地图)
    render() {
        const color_even = "#AAD751";          //偶数
        const color_odd = "#A2D149"            //奇数

        for (let i = 0; i < this.rows; i++) {
            for (let j = 0; j < this.cols; j++) {
                if ((i + j) % 2 == 0)
                    this.ctx.fillStyle = color_even;
                else
                    this.ctx.fillStyle = color_odd;
                this.ctx.fillRect(j * this.L, i * this.L, this.L, this.L);
            }
        }
    }
}
